const fp = require("lodash/fp");
class Maybe {
  static of(value) {
    return new Container(value);
  }
  constructor(value) {
    this._value = value;
  }

  isNothing() {
    return this._value === null || this._value === undefined;
  }

  map(fn) {
    console.log(this.isNothing());
    return this.isNothing ? this : Maybe.of(fn(this._value));
  }
}

class Container {
  static of(value) {
    return new Container(value);
  }
  constructor(value) {
    this._value = value;
  }
  map(fn) {
    return Container.of(fn(this._value));
  }
}

let maybe = Maybe.of([5, 6, 1]);

// one
let ex1 = val => {
  return fp.map(fp.add(1), val)
}
// console.log(maybe.map(ex1)); // Container { _value: [ 6, 7, 2 ] }


// two
let xs = Container.of(['do', 'rey', 'mi', 'fa', 'so', 'la', 'ti', 'do']);
let ex2 = val => {
  return fp.first(val) 
}

// console.log(xs.map(ex2)); // Container { _value: 'do' }


// three
let safeProp = fp.curry(function(x, o) {
  return Maybe.of(o[x])
})

let user = {id: 1, name: 'Albert'}

let ex3 = () => {
  return safeProp('name', user).map(fp.first)
}

// console.log(ex3());


// four
// let ex4 = n => {
//   if(n){
//     parseInt(n)
//   }
// }

let ex4 = (n) => {
  return Maybe.of(n).map(val => parseInt(val))
}

// console.log(ex4(4.333)); // Container { _value: 4 }
console.log(ex4(null)); // Container { _value:  }


